import { message } from 'antd';
import { useEffect, useState } from 'react';
import type { Layout } from 'react-grid-layout';
import DragItemPanel from '@/components/Template/DragItemPanel';
import DropItemFormPanel from '@/components/Template/DropItemFormPanel';
import DropItemPanel from '@/components/Template/DropItemPanel';
import { useStyles } from '@/components/Template/styles';
import type {
  DragItemType,
  FormValuesType,
  TemplateType,
} from '@/types/template';

interface TemplateContainerProps {
  type: TemplateType;
  template: DragItemType[];
  dataSource?: Record<string, unknown>;
  onTemplateChange?: (template: DragItemType[]) => void;
  onValueChange?: (item: DragItemType, value: string, reason?: string) => void;
}
export default function TemplateContainer({
  type,
  template,
  dataSource,
  onTemplateChange,
  onValueChange,
}: TemplateContainerProps) {
  const { styles } = useStyles();
  const [isDropZoneOver, setIsDropZoneOver] = useState(false);
  const [draggedItem, setDraggedItem] = useState<DragItemType | null>(null);
  const [addedItems, setAddedItems] = useState<DragItemType[]>([]);
  const [editItem, setEditItem] = useState<DragItemType | null>(null);
  // 处理拖动开始
  const handleDragStart = (item: DragItemType) => {
    const y = 100;
    if (item.type === 'Custom' || item.type === 'Empty') {
      setDraggedItem({
        ...item,
        id: Date.now(),
        y,
      });
    } else {
      setDraggedItem({ ...item, y });
    }
  };
  // 处理拖动结束
  const handleDragEnd = (e: React.DragEvent<HTMLElement>) => {
    e.preventDefault();
    setEditItem(draggedItem);
    setDraggedItem(null);
    setIsDropZoneOver(false);
  };
  // 处理放置
  const handleDrop = (e: React.DragEvent<HTMLElement>) => {
    e.preventDefault();
    setIsDropZoneOver(false);
    // 检查是否已存在相同组件
    const currentItem = addedItems.find((item) => item.id === draggedItem!.id);
    if (currentItem) {
      message.error('已存在相同组件');
      return;
    }
    setAddedItems([draggedItem!, ...addedItems]);
  };
  // 添加区域组件点击事件
  const handleAddItemClick = (item: DragItemType) => {
    setEditItem(item);
  };
  // 删除组件
  const handleItemDelete = (item: DragItemType) => {
    setAddedItems(addedItems.filter((cur) => cur.id !== item.id));
    setEditItem(null);
  };
  // 布局发生变化
  const handleLayoutChange = (currentLayout: Layout[]) => {
    const currentTemplate = addedItems.map((item) => {
      const layout = currentLayout.find(
        (layout) => layout.i === item.id.toString(),
      );
      if (layout) {
        return {
          ...item,
          x: layout.x,
          y: layout.y,
          w: layout.w,
          h: layout.h,
        };
      }
      return item;
    });
    setAddedItems(currentTemplate);
    onTemplateChange?.(currentTemplate);
  };
  const handleFormValuesChange = (
    _changedValues: Partial<FormValuesType>,
    allValues: FormValuesType,
  ) => {
    console.log(allValues);
    const currentTemplate = addedItems.map((item) => {
      if (item.id === editItem!.id) {
        return {
          ...item,
          ...allValues,
        };
      }
      return item;
    });
    setAddedItems(currentTemplate);
    onTemplateChange?.(currentTemplate);
  };
  const handleValueChange = (
    item: DragItemType,
    value: string,
    reason?: string,
  ) => {
    setAddedItems(
      addedItems.map((i) => {
        if (i.id === item.id) {
          return {
            ...i,
            value,
            reason,
          };
        }
        return i;
      }),
    );
    onValueChange?.(item, value, reason);
  };
  useEffect(() => {
    // 如果没有数据直接渲染模板
    if (!dataSource) {
      setAddedItems(template);
      return;
    }
    // 如果有数据，将数据映射到模板后渲染模板
    const templateFillData = template.map((item) => ({
      ...item,
      value:
        (dataSource[item.field as keyof typeof dataSource] as string) || '',
    }));
    setAddedItems(templateFillData);
  }, [template, dataSource]);
  return (
    <div className={styles.templatePage}>
      {type === 'edit' && (
        <DragItemPanel
          draggedItem={draggedItem}
          onDragStart={handleDragStart}
          onDragEnd={handleDragEnd}
        />
      )}
      <DropItemPanel
        type={type}
        addedItems={addedItems}
        isDropZoneOver={isDropZoneOver}
        onDrop={handleDrop}
        onDragEnter={() => setIsDropZoneOver(true)}
        onDragLeave={() => setIsDropZoneOver(false)}
        onItemClick={handleAddItemClick}
        onItemDelete={handleItemDelete}
        onLayoutChange={handleLayoutChange}
        onValueChange={handleValueChange}
      />
      {type === 'edit' && (
        <DropItemFormPanel
          editItem={editItem}
          onValuesChange={handleFormValuesChange}
        />
      )}
    </div>
  );
}
